from fastapi import Depends, HTTPException
from fastapi.security import HTTPBearer, HTTPAuthorizationCredentials, OAuth2PasswordBearer
from typing import Optional, Annotated

from pydantic import BaseModel
from starlette.requests import Request

from app.utils.jwt_service import verify_jwt

oauth2_scheme = OAuth2PasswordBearer(tokenUrl="token")

class JWTUser(BaseModel):
    account: str = None
    token: str = None


class JWTAuthorizationCredentials(HTTPAuthorizationCredentials):
    user: JWTUser


class JWTBearer(HTTPBearer):
    def __init__(self, auto_error: bool = True):
        super(JWTBearer, self).__init__(auto_error=auto_error)

    async def __call__(self, request: Request):
        # 过滤不需要验证的路径
        path = request.get("path")
        if path.startswith("/login") or path.startswith("/static") or path.startswith("/home/banner"):
            return None
        credentials: HTTPAuthorizationCredentials = await super(JWTBearer, self).__call__(request)
        if credentials:
            if not credentials.scheme == "Bearer":
                raise HTTPException(status_code=403, detail="无效的身份验证方案。")
            if not self.verify_jwt(credentials.credentials):
                raise HTTPException(status_code=403, detail="令牌无效或令牌过期。")
            return credentials.credentials
        else:
            raise HTTPException(status_code=403, detail="授权码无效。")

    @staticmethod
    def verify_jwt(jwtoken: str) -> bool:
        is_token_valid: bool = False

        try:
            payload = verify_jwt(jwtoken)
        except:
            payload = None
        if payload:
            is_token_valid = True
        return is_token_valid


def get_current_user(token: Annotated[str, Depends(oauth2_scheme)]):
    return verify_jwt(token)
